package vcp.client.GUI.mvc.view;

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.Font;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;

import javax.swing.Box;
import javax.swing.DefaultComboBoxModel;
import javax.swing.ImageIcon;
import javax.swing.JButton;
import javax.swing.JComboBox;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JTable;
import javax.swing.JTextField;
import javax.swing.SwingConstants;
import javax.swing.border.EtchedBorder;
import javax.swing.border.MatteBorder;
import javax.swing.table.DefaultTableCellRenderer;
import javax.swing.table.DefaultTableModel;
import javax.swing.table.TableCellRenderer;

import org.joda.time.DateTime;
import org.joda.time.format.DateTimeFormat;
import org.joda.time.format.DateTimeFormatter;

import vcp.client.GUI.events.FormSubmitionEvent;
import vcp.client.GUI.mvc.view.addons.JCalendarWrapper;
import vcp.client.GUI.mvc.view.addons.TableColumnAdjuster;
import vcp.client.GUI.mvc.view.custom.CustomCalendarIconButton;
import vcp.client.forms.PeriodicForm;
import vcp.client.interfaces.listeners.IFormSubmitionListener;
import vcp.client.reports.ReportAbstract;
import vcp.client.utility.Common;
import vcp.client.utility.Common.UserNotification;
import vcp.client.utility.UtilityHelper;
import vcp.enums.PopUpMessageType;
import vcp.enums.ReportType;

/**
 * 
 * @author VCP team
 *         <p>
 *         View responsible presenting user different reports according to
 *         different time periods
 *         </p
 */
public class UIQuarterReportsView extends UIAbstractView
{

	/**
	 * 
	 */
	private static final long serialVersionUID = - 8461079956325791154L;
	private JTextField tfStartDate;
	private JTextField tfEndDate;
	private JButton btnSearch;
	private JButton btnSave;

	private JComboBox <ReportType> cbReportType;
	private JLabel lblFoundReport;

	// ****************************************************************************************************************************
	// Setter-Getter methods
	// ****************************************************************************************************************************
	private IFormSubmitionListener <PeriodicForm> formSubmitionListener;
	private JTable table;

	public void setFormSubmitionListener ( IFormSubmitionListener <PeriodicForm> formSubmitionListener )
	{
		this.formSubmitionListener = formSubmitionListener;
	}

	public UIQuarterReportsView ()
	{
		super();
	}

	// ****************************************************************************************************************************
	// Public methods
	// ****************************************************************************************************************************
	public void loadReport ( ReportAbstract report )
	{
		boolean saveEnable = false;

		DefaultTableModel dtm = new DefaultTableModel();
		if ( report != null )
		{
			// if received an instance of EmptyReport - no data was found in DB
			if ( report.isEmptyReport() )
			{
				this.lblFoundReport.setText("Cannot find data for current time period");
			}

			// otherwise put report data into table
			else
			{
				for ( String header : report.getHeaders() )
				{
					dtm.addColumn(header);
				}

				for ( Object[] object : report.getRows() )
				{
					dtm.addRow(object);
				}

				new TableColumnAdjuster(this.table).adjustColumns();
				saveEnable = true;
			}
		}

		// replaces old model
		this.table.setModel(dtm);

		// save button will be enabled only when data is presented to user
		this.btnSave.setEnabled(saveEnable);
	}

	// ****************************************************************************************************************************
	// Private methods
	// ****************************************************************************************************************************
	/**
	 * @return true when period start & end were filled
	 */
	private boolean hasStartAndEndDate ()
	{
		return UtilityHelper
				.getUtilityHelperInstance()
				.isParamsNotNull(this.tfStartDate.getText(), this.tfEndDate.getText());
	}

	/**
	 * @return the chosen report type
	 */
	private ReportType getSelectedReportType ()
	{
		return (ReportType) this.cbReportType.getSelectedItem();
	}

	// ****************************************************************************************************************************
	// UIAbstractView methods
	// ****************************************************************************************************************************
	@Override
	protected void setupLayout ()
	{
		this.setPreferredSize(new Dimension(908, 704));
		this.setLayout(new BorderLayout(0, 0));

		JPanel panel = new JPanel();
		panel.setBorder(new MatteBorder(0, 0, 1, 0, new Color(0, 0, 0)));
		this.add(panel, BorderLayout.NORTH);
		panel.setLayout(new BorderLayout(0, 0));

		JPanel panel_1 = new JPanel();
		panel.add(panel_1, BorderLayout.WEST);

		JLabel lblNewLabel = new JLabel("Start Date:");
		lblNewLabel.setFont(new Font("Lucida Grande", Font.PLAIN, 18));
		panel_1.add(lblNewLabel);

		this.tfStartDate = new JTextField();
		this.tfStartDate.setPreferredSize(new Dimension(125, 28));
		this.tfStartDate.setFont(new Font("Lucida Grande", Font.PLAIN, 18));
		this.tfStartDate.setEditable(false);
		panel_1.add(this.tfStartDate);

		CustomCalendarIconButton btnStartDate = new CustomCalendarIconButton(this.tfStartDate);
		btnStartDate.setPreferredSize(new Dimension(30, 25));
		panel_1.add(btnStartDate);

		Component horizontalStrut = Box.createHorizontalStrut(20);
		panel_1.add(horizontalStrut);

		JLabel lblEndDate = new JLabel("End Date:");
		lblEndDate.setFont(new Font("Lucida Grande", Font.PLAIN, 18));
		panel_1.add(lblEndDate);

		this.tfEndDate = new JTextField();
		this.tfEndDate.setPreferredSize(new Dimension(125, 28));
		this.tfEndDate.setFont(new Font("Lucida Grande", Font.PLAIN, 18));
		this.tfEndDate.setEditable(false);
		panel_1.add(this.tfEndDate);

		CustomCalendarIconButton btnEndDate = new CustomCalendarIconButton(this.tfEndDate);
		btnEndDate.setPreferredSize(new Dimension(30, 25));
		panel_1.add(btnEndDate);

		Component horizontalStrut_2 = Box.createHorizontalStrut(20);
		panel_1.add(horizontalStrut_2);

		this.cbReportType = new JComboBox <>();
		this.cbReportType.setFont(new Font("Lucida Grande", Font.PLAIN, 15));
		this.cbReportType.setModel(new DefaultComboBoxModel <ReportType>(ReportType.siteManagerReports()));
		panel_1.add(this.cbReportType);

		this.btnSearch = new JButton(Common.BTN_SEARCH);
		this.btnSearch.setFont(new Font("Lucida Grande", Font.PLAIN, 18));
		this.btnSearch.setActionCommand(Common.BTN_SEARCH);
		panel.add(this.btnSearch, BorderLayout.EAST);

		JPanel panel_2 = new JPanel();
		this.add(panel_2, BorderLayout.CENTER);
		panel_2.setLayout(new BorderLayout(0, 0));

		JPanel panel_9 = new JPanel();
		panel_9.setPreferredSize(new Dimension(10, 35));
		FlowLayout flowLayout = (FlowLayout) panel_9.getLayout();
		flowLayout.setAlignment(FlowLayout.LEFT);
		panel_2.add(panel_9, BorderLayout.NORTH);

		this.lblFoundReport = new JLabel("");
		this.lblFoundReport.setFont(new Font("Lucida Grande", Font.PLAIN, 18));
		panel_9.add(this.lblFoundReport);

		JPanel panel_11 = new JPanel();
		panel_2.add(panel_11, BorderLayout.CENTER);
		panel_11.setLayout(new BorderLayout(0, 0));

		JScrollPane scrollPane = new JScrollPane();
		panel_11.add(scrollPane, BorderLayout.CENTER);

		final DefaultTableCellRenderer renderRight = new DefaultTableCellRenderer();

		renderRight.setHorizontalAlignment(SwingConstants.CENTER);

		this.table = new JTable()
			{
				/**
			 * 
			 */
				private static final long serialVersionUID = 1L;

				@Override
				public boolean isCellEditable ( int row, int column )
				{
					return false;
				}

				@Override
				public void setRowHeight ( int rowHeight )
				{
					super.setRowHeight(45);
				}

				@Override
				public TableCellRenderer getCellRenderer ( int arg0, int arg1 )
				{
					return renderRight;
				}
			};
		this.table.setGridColor(Color.BLACK);
		this.table.setShowHorizontalLines(true);
		this.table.setShowVerticalLines(true);
		this.table.setBorder(new EtchedBorder(EtchedBorder.RAISED));
		this.table.setShowGrid(true);
		this.table.setFont(new Font("Lucida Grande", Font.PLAIN, 18));

		scrollPane.setViewportView(this.table);
		JPanel panel_10 = new JPanel();
		panel_10.setPreferredSize(new Dimension(10, 200));
		panel_2.add(panel_10, BorderLayout.SOUTH);

		JPanel panel_3 = new JPanel();
		this.add(panel_3, BorderLayout.SOUTH);
		panel_3.setPreferredSize(new Dimension(10, 60));
		panel_3.setLayout(new GridLayout(0, 6, 0, 0));

		JPanel panel_4 = new JPanel();
		panel_3.add(panel_4);

		JPanel panel_5 = new JPanel();
		panel_3.add(panel_5);

		JPanel panel_8 = new JPanel();
		panel_3.add(panel_8);

		JPanel panel_7 = new JPanel();
		panel_3.add(panel_7);

		JPanel panel_6 = new JPanel();
		panel_3.add(panel_6);

		this.btnSave = new JButton(Common.BTN_SAVE);
		this.btnSave.setEnabled(false);
		this.btnSave.setActionCommand(Common.BTN_SAVE);
		this.btnSave.setName(Common.BTN_SAVE);
		this.btnSave.setFont(new Font("Lucida Grande", Font.PLAIN, 16));
		panel_3.add(this.btnSave);
	}

	@Override
	protected void setupListeners ()
	{
		this.btnSearch.addActionListener(this);
		this.btnSave.addActionListener(this);
	}

	@Override
	protected void setupButtonsIcons ()
	{
		int iconTextGap = 20;

		ImageIcon icon = UtilityHelper.getUtilityHelperInstance().loadScaledImage(Common.ICON_SAVE, 40, 40);
		if ( icon != null )
		{
			this.btnSave.setIcon(icon);
			this.btnSave.setIconTextGap(iconTextGap);
		}

		icon = UtilityHelper.getUtilityHelperInstance().loadScaledImage(Common.ICON_SEARCH, 30, 30);
		if ( icon != null )
		{
			this.btnSearch.setIcon(icon);
			// this.btnSearch.setIconTextGap(iconTextGap);
		}
	}

	// ****************************************************************************************************************************
	// ActionListener methods
	// ****************************************************************************************************************************
	@Override
	public void actionPerformed ( ActionEvent actionEvent )
	{
		// detected the button triggered action event
		switch ( actionEvent.getActionCommand() )
		{
			case Common.BTN_SEARCH:
				// if both periods were fulfilled
				if ( this.hasStartAndEndDate() )
				{
					this.lblFoundReport.setText("");

					DateTimeFormatter formatter = DateTimeFormat.forPattern(JCalendarWrapper.getCalendarDateFormat());
					DateTime startDate = formatter.parseDateTime(this.tfStartDate.getText());
					DateTime endDate = formatter.parseDateTime(this.tfEndDate.getText());
					if ( this.formSubmitionListener != null )
					{
						// fire event using formSubmitionListener delegate
						this.formSubmitionListener.onFormSubmitted(new FormSubmitionEvent <>(this, new PeriodicForm(startDate, endDate, this.getSelectedReportType())));
					}
				}
				else
				{
					// presenting notification to user, start & end need to be
					// filled
					this.controllerDelegate.showPopUpMessage(UserNotification.MUST_FILL_START_AND_END_DATE, PopUpMessageType.INFORMATION);
				}
				break;

			case Common.BTN_SAVE:
				if ( this.controllerDelegate != null )
				{
					// fire event using controllerDelegate delegate to save
					// current report
					this.controllerDelegate.onButtonPress(null);
				}
				break;
		}
	}
}
